<?php

// [ H5 统一下单 ]
// use app\common\lib\Order as OrderCommonLib;
// $title = '续费';
// $money = 0.01;
// $res   = OrderCommonLib::run($title,$money[,$notifyUrl]);
// p($res);die;

namespace app\common\lib;
use think\Db;
use think\facade\Config;
use think\facade\Request;

class Order
{
    // title      商品名称
    // money      付款金额（单位：分）
    // notifyUrl  支付结果通知的回调地址
    public static function run($title, $days, $money, $mobile, $notifyUrl = '')
    {
        $url = 'https://api.mch.weixin.qq.com/pay/unifiedorder';

        $arr = [
            'appid'            => Config::get('wx.appid'),
            'mch_id'           => Config::get('wx.mch_id'),
            'nonce_str'        => mkstr(32,0),
            'body'             => Config::get('wx.title') . '-' . $title,
            'out_trade_no'     => date('YmdHis') . rand(100000,999999),
            'total_fee'        => $money * 100,
            'spbill_create_ip' => Request::ip(),
            'notify_url'       => empty($notifyUrl) ? Config::get('wx.pay_callback_url') : $notifyUrl,
            'trade_type'       => 'MWEB',
            'scene_info'       => '{"h5_info": {"type":"Wap","wap_url": "' . Config::get('wx.host') . '","wap_name": "' . Config::get('wx.title') . '"}}',
        ];

        // 字典序排序
        ksort($arr);
        // p($arr);die;

        // 签名
        $arr['sign'] = self::_signature($arr);
        // p($arr);die;

        // 转xml
        $xml  = '<xml>';
        foreach ($arr as $key => $val) {
            $xml .= '<' . $key . '>' . $val . '</' . $key . '>';
        }
        $xml .= '</xml>';
        // p($xml);die;

        $res = https_curl($url,'POST',$xml);
        // p($res);die;
        $res = xml_to_array($res);
        // p($res);die;
        
        // # 写入订单表
        // -------------------------------------------------------------------------
        $data['mobile']       = $mobile;
        $data['days']         = $days;
        $data['money']        = $money;
        $data['out_trade_no'] = $arr['out_trade_no'];
        $data['status']       = 0;
        $data['create_time']  = time();
        Db::name('order')->insert($data);
        // -------------------------------------------------------------------------

        $arr = [
            'out_trade_no' => $arr['out_trade_no'],
            'data'         => $res,
        ];
        return $arr;
    }

    /* 签名
    第一步，设所有发送或者接收到的数据为集合M，将集合M内非空参数值的参数按照参数名ASCII码从小到大排序（字典序），
            使用URL键值对的格式（即key1=value1&key2=value2…）拼接成字符串stringA。
            特别注意以下重要规则：
            ◆ 参数名ASCII码从小到大排序（字典序）；
            ◆ 如果参数的值为空不参与签名；
            ◆ 参数名区分大小写；
            ◆ 验证调用返回或微信主动通知签名时，传送的sign参数不参与签名，将生成的签名与该sign值作校验。
            ◆ 微信接口可能增加字段，验证签名时必须支持增加的扩展字段
    第二步，在stringA最后拼接上key得到stringSignTemp字符串，并对stringSignTemp进行MD5运算，再将得到的字符串所有字符转换为大写，
            得到sign值signValue。
            ◆ key设置路径：微信商户平台(pay.weixin.qq.com)-->账户设置-->API安全-->密钥设置
    */
    private static function _signature($arr)
    {
        // 用URL键值对的格式拼接成字符串
        // $stringA  = http_build_query($arr);
        // 生成 URL-encode 之后的请求字符串
        $str = '';
        foreach ($arr as $key => $val) {
            $str .= '&' . $key . '=' . $val;
        }
        $stringA = substr($str,1);

        // p($stringA);

        // 拼接商户平台key
        $stringA .= '&key=' . Config::get('wx.key');

        // p($stringA);

        // md5加密
        $stringSignTemp = md5($stringA);

        // 转大写
        $signValue = strtoupper($stringSignTemp);

        return $signValue;
    }
}